/*!
 * jQuery Birthday Picker: v1.4 - 10/16/2011
 * http://abecoffman.com/stuff/birthdaypicker
 *
 * Copyright (c) 2010 Abe Coffman
 * Dual licensed under the MIT and GPL licenses.
 *
 */

(function ($) {

    // plugin variables
    var months = {
            "short": ["01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12"]
        },
        todayDate = new Date(),
        todayYear = todayDate.getFullYear(),
        todayMonth = todayDate.getMonth() + 1,
        todayDay = todayDate.getDate(),
        months1 = {
            "short1": ["00","01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12", "13", "14", "15", "16", "17", "18", "19", "20", "21", "22", "23", "24", "25", "26", "27", "28", "29", "30", "31"]
        };

    $.fn.birthdaypicker = function (options) {

        var settings = {
            "maxAge": 100,
            "minAge": 0,
            "futureDates": false,
            "maxYear": todayYear,
            "dateFormat": "middleEndian",
            "monthFormat": "short",
            "monthFormat1": "short1",
            "placeholder": true,
            "defaultDate": false,
            "fieldName": "birthdate",
            "fieldId": "birthdate",
            "hiddenDate": true,
            "onChange": null,
            "tabindex": null,
            "wraper": "fieldset",
            "legend": "",
        };

        return this.each(function () {

            if (options) {
                $.extend(settings, options);
            }

            // Create the html picker skeleton
            var _wrap = "<" + "div " + " class='birthday-picker'></" + "div" + ">";

            // var $wraper = $("<fieldset class='birthday-picker'></fieldset>"),
            var $wraper = $(_wrap),
                $year = $("<select class='birth-year' name='birth[year]'></select>"),
                $month = $("<select class='birth-month' name='birth[month]'></select>"),
                $day = $("<select class='birth-day' name='birth[day]'></select>");

            if (settings["legend"]) {
                $("<legend>" + settings["legend"] + "</legend>").appendTo($wraper);
            }

            var tabindex = settings["tabindex"];

            // Deal with the various Date Formats
            if (settings["dateFormat"] == "bigEndian") {
                $wraper.append($year).append($month).append($day);
                if (tabindex != null) {
                    $year.attr('tabindex', tabindex);
                    $month.attr('tabindex', tabindex++);
                    $day.attr('tabindex', tabindex++);
                }
            } else if (settings["dateFormat"] == "littleEndian") {
                $wraper.append($day).append($month).append($year);
                if (tabindex != null) {
                    $day.attr('tabindex', tabindex);
                    $month.attr('tabindex', tabindex++);
                    $year.attr('tabindex', tabindex++);
                }
            } else {
                $wraper.append($month).append($day).append($year);
                if (tabindex != null) {
                    $month.attr('tabindex', tabindex);
                    $day.attr('tabindex', tabindex++);
                    $year.attr('tabindex', tabindex++);
                }
            }

            // Add the option placeholders if specified
            if (settings["placeholder"]) {
                $("<option value='0'>年</option>").appendTo($year);
                $("<option value='0'>月</option>").appendTo($month);
                $("<option value='0'>日</option>").appendTo($day);
            }

            var hiddenDate;
            if (settings["defaultDate"]) {
                var defDate = new Date(settings["defaultDate"] + "T00:00:00"),
                    defYear = defDate.getFullYear(),
                    defMonth = defDate.getMonth() + 1,
                    defDay = defDate.getDate();
                if (defMonth < 10) defMonth = "0" + defMonth;
                if (defDay < 10) defDay = "0" + defDay;
                hiddenDate = defYear + "-" + defMonth + "-" + defDay;
            }

            // Create the hidden date markup
            if (settings["hiddenDate"]) {
                $("<input type='hidden' name='" + settings["fieldName"] + "'/>")
                    .attr("id", settings["fieldId"])
                    .val(hiddenDate)
                    .appendTo($wraper);
            }

            // Build the initial option sets
            var startYear = todayYear - settings["minAge"];
            var endYear = todayYear - settings["maxAge"];
            if (settings["futureDates"] && settings["maxYear"] != todayYear) {
                if (settings["maxYear"] > 1000) {
                    startYear = settings["maxYear"];
                } else {
                    startYear = todayYear + settings["maxYear"];
                }
            }
            for (var i = startYear; i >= endYear; i--) {
                $("<option></option>").attr("value", i).text(i).appendTo($year);
            }
            for (var j = 0; j < 12; j++) {
                $("<option></option>").attr("value", months[settings["monthFormat"]][j]).text(months[settings["monthFormat"]][j]).appendTo($month);
            }
            for (var k = 1; k < 32; k++) {
                $("<option></option>").attr("value", months1[settings["monthFormat1"]][k]).text(k).appendTo($day);
            }
            $(this).append($wraper);

            // Set the default date if given
            if (settings["defaultDate"]) {
                var date = new Date(settings["defaultDate"] + "T00:00:00");
                $year.val(date.getFullYear());
                $month.val(date.getMonth() + 1);
                $day.val(date.getDate());
            }

            // Update the option sets according to options and user selections
            $wraper.change(function () {
                // todays date values
                var todayDate = new Date(),
                    todayYear = todayDate.getFullYear(),
                    todayMonth = todayDate.getMonth() + 1,
                    todayDay = todayDate.getDate(),
                    // currently selected values
                    selectedYear = parseInt($year.val(), 10),
                    selectedMonth = parseInt($month.val(), 10),
                    selectedDay = parseInt($day.val(), 10),
                    // number of days in currently selected year/month
                    actMaxDay = (new Date(selectedYear, selectedMonth, 0)).getDate(),
                    // max values currently in the markup
                    curMaxMonth = parseInt($month.children(":last").val()),
                    curMaxDay = parseInt($day.children(":last").val());

                // Dealing with the number of days in a month
                // http://bugs.jquery.com/ticket/3041
                if (curMaxDay > actMaxDay) {
                    while (curMaxDay > actMaxDay) {
                        $day.children(":last").remove();
                        curMaxDay--;
                    }
                } else if (curMaxDay < actMaxDay) {
                    while (curMaxDay < actMaxDay) {
                        curMaxDay++;
                        $day.append("<option value=" + curMaxDay + ">" + curMaxDay + "</option>");
                    }
                }

                // Dealing with future months/days in current year
                // or months/days that fall after the minimum age
                if (!settings["futureDates"] && selectedYear == startYear) {
                    if (curMaxMonth > todayMonth) {
                        while (curMaxMonth > todayMonth) {
                            $month.children(":last").remove();
                            curMaxMonth--;
                        }
                        // reset the day selection
                        $day.children(":first").attr("selected", "selected");
                    }
                    if (selectedMonth === todayMonth) {
                        while (curMaxDay > todayDay) {
                            $day.children(":last").remove();
                            curMaxDay -= 1;
                        }
                    }
                }

                // Adding months back that may have been removed
                // http://bugs.jquery.com/ticket/3041
                if (selectedYear != startYear && curMaxMonth != 12) {
                    while (curMaxMonth < 12) {
                        $month.append("<option value=" + (curMaxMonth + 1) + ">" + months[settings["monthFormat"]][curMaxMonth] + "</option>");
                        curMaxMonth++;
                    }
                }

                // update the hidden date
                if ((selectedYear * selectedMonth * selectedDay) != 0) {
                    if (selectedMonth < 10) selectedMonth = "0" + selectedMonth;
                    if (selectedDay < 10) selectedDay = "0" + selectedDay;
                    hiddenDate = selectedYear + "-" + selectedMonth + "-" + selectedDay;
                    $(this).find('#' + settings["fieldId"]).val(hiddenDate);
                    if (settings["onChange"] != null) {
                        settings["onChange"](hiddenDate);
                    }
                } else {
                    hiddenDate = "";
                    $(this).find('#' + settings["fieldId"]).val(hiddenDate);
                }
            });
        });
    };
})(jQuery);